﻿using System;
using System.Collections;
using System.ComponentModel;
using System.Diagnostics;
using System.IO;
using System.Windows.Forms;
using KillBot.Properties;
using Microsoft.Win32;

namespace AutoKillThing
{
    public partial class MainForm : Form
    {
        #region Member Variables

        private Timer killCheck;
        private bool isRunning = false;
        private bool writeKey = false; 

        #endregion

        #region Form Events

        public MainForm()
        {
            InitializeComponent();
        }

        private void MainForm_Load(object sender, EventArgs e)
        {
            KillList.Load();

            foreach (DictionaryEntry de in KillList.ActiveKills)
            {
                LstKillList.Items.Add(de.Key.ToString(), Boolean.Parse(de.Value.ToString()));
            }

            killCheck = new Timer()
            {
                Interval = 3000
            };

            killCheck.Tick += new EventHandler(killCheck_Tick);

            /** check the registry to see if we are set to start with windows **/
            ChkStartup.Checked = GetAutoStart();
            /** and the rest of the settings **/
            ChkLog.Checked = Settings.Default.LogKills;
            ChkNotify.Checked = Settings.Default.NotifyOnKill;

        }

        private void MainForm_Resize(object sender, EventArgs e)
        {
            if (WindowState == FormWindowState.Minimized)
            {
                Hide();
            }
        } 

        #endregion

        #region Kill Handlers

        private void killCheck_Tick(object sender, EventArgs e)
        {
            Process[] ps = Process.GetProcesses();

            for (int i = 0; i < ps.Length - 1; i++)
            {
                try
                {
                    string t = ps[i].ProcessName;
                    string fileName = Path.GetFileNameWithoutExtension(t);
                    foreach (DictionaryEntry item in KillList.ActiveKills)
                    {
                        if (item.Key.ToString().Contains(t))
                        {
                            string tst = item.Value.ToString();
                            if (tst == "True")
                            {

                                ps[i].Kill();
                                ps[i].WaitForExit();
                                if (Settings.Default.LogKills)
                                {
                                    LogKill(t);
                                }
                                if (Settings.Default.NotifyOnKill)
                                {
                                    notifyIcon1.ShowBalloonTip(2, "Succesful Kill!", t + " has been successfully eliminated", ToolTipIcon.None);
                                }
                            }

                        }
                    }
                }

                catch (Win32Exception)
                {

                    continue;
                }
            }
        }

        private void LogKill(string theProcess)
        {
            StreamWriter sw = new StreamWriter(Settings.Default.LogPath, true);
            string outLine = DateTime.Now.ToLongTimeString() + " -> " + theProcess;

            sw.WriteLine(outLine);
            sw.Close();

        }

        #endregion  

        #region KillList

        private void CmdAddKill_Click(object sender, EventArgs e)
        {
            FrmInput frm = new FrmInput();
            DialogResult result = frm.ShowDialog();

            if (result != DialogResult.OK || frm.answer.Length == 0)
            {
                return;
            }

            string str = frm.answer;
            if (KillList.Add(str) == 0)
            {
                LstKillList.Items.Add(str, true);
            }
        }

        private void CmdRemoveKill_Click(object sender, EventArgs e)
        {
            string x = LstKillList.SelectedItem.ToString();
            KillList.Remove(x);
            LstKillList.Items.Remove(x);
        }

        private void LstKillList_SelectedValueChanged(object sender, EventArgs e)
        {
            CheckedListBox clb = (CheckedListBox)sender;
            CmdRemoveKill.Enabled = true;
            if (clb.SelectedIndex == -1)
            {
                return;
            }
            if (clb.GetItemCheckState(clb.SelectedIndex) == CheckState.Checked)
            {
                KillList.ChangeStatus(clb.SelectedItem.ToString(), true);
                return;
            }
            KillList.ChangeStatus(clb.SelectedItem.ToString(), false);
        } 

        #endregion

        #region Settings

        private void CmdStartStop_Click(object sender, EventArgs e)
        {
            if (isRunning)
            {
                killCheck.Stop();
                CmdStartStop.Text = "Start";
                isRunning = false;
            }
            else
            {
                killCheck.Start();
                CmdStartStop.Text = "Stop";
                isRunning = true;

            }


        }



        private void CmdSave_Click(object sender, EventArgs e)
        {

            if (ChkNotify.CheckState == CheckState.Checked)
            {
                Settings.Default.NotifyOnKill = true;
            }
            else
            {
                Settings.Default.NotifyOnKill = false;
            }

            if (ChkLog.CheckState == CheckState.Checked)
            {
                Settings.Default.LogKills = true;
            }
            else
            {
                Settings.Default.LogKills = false;
            }
            

            if (writeKey)
            {
                SetAutoStart(ChkStartup.Checked);
                writeKey = false;
            }

            Settings.Default.Save();
            Settings.Default.Reload();
            CmdSave.Enabled = false;
            lblStatus.Text = "Settings Saved";
        }

        private void ChkStartup_CheckedChanged(object sender, EventArgs e)
        {
            writeKey = true;
            CmdSave.Enabled = true;
            lblStatus.Text = string.Empty;
        }

        private void ChkNotify_CheckedChanged(object sender, EventArgs e)
        {
            CmdSave.Enabled = true;
            lblStatus.Text = string.Empty;
        }

        #endregion

        #region Try Icon

        private void CtxExitProgram_Click(object sender, EventArgs e)
        {
            Close();
        }

        private void notifyIcon1_MouseDoubleClick(object sender, MouseEventArgs e)
        {
            if (Visible)
            {
                Hide();
                return;
            }
            Show();
            BringToFront();
        } 

        #endregion

        #region Utility

        /// <summary>
        /// Creates the autostart key if true, deletes it if false
        /// </summary>
        /// <param name="createKey">true = write, false = delete</param>
        private void SetAutoStart(bool createKey)
        {
            var rk = Registry.CurrentUser.OpenSubKey("SOFTWARE\\Microsoft\\Windows\\CurrentVersion\\Run", true);


            /** no need to write the key if it alread exists **/
            if (createKey == true && GetAutoStart() == false)
            {
                /** create the key **/
                rk.SetValue("KillBot", Application.ExecutablePath.ToString());
                return;
            }

            /** get rid of autostart entry **/
            rk.DeleteValue("KillBot", false);
        }

        /// <summary>
        /// Get the value in the autostart key
        /// </summary>
        /// <returns>true if key exists (on), false if it doesn't (off)</returns>
        private bool GetAutoStart()
        {
            var rk = Registry.CurrentUser.OpenSubKey("SOFTWARE\\Microsoft\\Windows\\CurrentVersion\\Run", true);

            if (rk.GetValue("KillBot") == null)
            {
                return false;
            }
            return true;
        } 

        #endregion

    }
}
